/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package cn.ekuma.epos.bean.util.erp;

import com.openbravo.data.loader.LocalRes;
import com.openbravo.format.Formats;
import com.openbravo.bean.BusinessPartner;
import com.openbravo.bean.PaymentInfo;
import com.openbravo.bean.PaymentInfoMagcard;
import com.openbravo.bean.Tax;
import com.openbravo.bean.infobean.UserInfo;
import com.openbravo.bean.erp.Order;
import com.openbravo.bean.erp.OrderLine;
import com.openbravo.bean.erp.OrderState;
import com.openbravo.bean.erp.OrderType;
import com.openbravo.bean.shard.IncludeTaxs;
import com.openbravo.pos.util.RoundUtils;
import com.openbravo.pos.util.StringUtils;
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectOutput;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

/**
 *
 * @author Administrator
 */
public class OrderHelper {

    private static DateFormat m_dateformat = new SimpleDateFormat("yyyyMMddHHmmss");

    public static String generateOrderId(){
        return m_dateformat.format(new Date());
    }
    
    public static String printDate(Order order) {
        return Formats.TIMESTAMP.formatValue(order.getDate());
    }

    public static String printUser(Order order) {
        return order.getUser()== null ? "" : order.getUser().getName();
    }

    public static String printCustomer(Order order) {
        return order.getCustomer()== null ? "" : order.getCustomer().getName();
    }

    public static String printArticlesCount(Order order) {
        return Formats.DOUBLE.formatValue(new Double(getArticlesCount(order)));
    }

    public static String printSubTotal(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getSubTotal(order)));
    }

    public static String printPrefArticlesCount(Order order) {
        return Formats.INT.formatValue(new Integer(getPrefArticlesCount(order)));
    }

    public static String printPrefSubTotal(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getPrefSubTotal(order)));
    }

    public static  String printTax(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getTax(order)));
    }

    public static String printTotal(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getTotal(order)));
    }

    public static String printTotalPaid(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getTotalPaid(order)));
    }

    public static String printPriceRate(Order order) {
        return Formats.PERCENT.formatValue(order.getM_dPriceRate());
    }

        public static String printDefSubTotal(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getDefineSubTotal(order)));
    }

    public static String printDefTax(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getDefineTax(order)));
    }

    public static String printDefTotal(Order order) {
        return Formats.CURRENCY.formatValue(new Double(getDefineTotal(order)));
    }

    public static  double getDefineSubTotal(Order order) {
        double sum = 0.0;
        for (OrderLine line : order.getLines()) {
            sum =RoundUtils.add(sum, OrderLineHelper.getDefaultSubValue(line));
        }
        return sum;
    }

    public static double getDefineTax(Order order) {
        double sum = 0.0;
        for (OrderLine line : order.getLines()) {
            sum =RoundUtils.add(sum, OrderLineHelper.getDefaultTax(line));
        }
        return sum;
    }

    public static double getDefineTotal(Order order) {
        return RoundUtils.add(getDefineSubTotal(order), getDefineTax(order));
    }


    public static IncludeTaxs[] getTaxLines(Order order) {

        Map<String, IncludeTaxs> m = new HashMap<String, IncludeTaxs>();

        OrderLine oLine;
        for (Iterator<OrderLine> i = order.getLines().iterator(); i.hasNext();) {
            oLine = i.next();

            IncludeTaxs tx = m.get(oLine.getTaxInfo().getId());
            if (tx == null) {
                tx = new IncludeTaxs(oLine.getTaxInfo());
                m.put(tx.getTaxInfo().getId(), tx);
            }
            tx.add(OrderLineHelper.getSubValue(oLine));
        }

        // return dSuma;
        Collection<IncludeTaxs> avalues = m.values();
        return avalues.toArray(new IncludeTaxs[avalues.size()]);
    }

    public static double getArticlesCount(Order order) {
        double dArticles = 0.0;
        OrderLine oLine;

        for (Iterator<OrderLine> i = order.getLines().iterator(); i.hasNext();) {
            oLine = i.next();
            dArticles =RoundUtils.add(dArticles, oLine.getMultiply());
        }

        return dArticles;
    }

    public static int getPrefArticlesCount(Order order) {
        int prepCount = 0;
        OrderLine oLine;

        for (Iterator<OrderLine> i = order.getLines().iterator(); i.hasNext();) {
            oLine = i.next();
            if (oLine.isIsPrefSell()) {
                prepCount += oLine.getMultiply();
            }
        }
        return prepCount;
    }

    public static double getPrefSubTotal(Order order) {
        double sum = 0.0;
        for (OrderLine line : order.getLines()) {
            if (line.isIsPrefSell()) {
                sum =RoundUtils.add(sum, OrderLineHelper.getPrefSubValue(line));
            }
        }
        return sum;
    }

    public static double getSubTotal(Order order) {
        double sum = 0.0;
        for (OrderLine line : order.getLines()) {
            sum =RoundUtils.add(sum, OrderLineHelper.getSubValue(line));
        }
        return sum;
    }

    public static double getTax(Order order) {

        double sum = 0.0;
        if (order.hasTaxesCalculated()) {
            for (IncludeTaxs tax : order.getTaxes()) {
                sum =RoundUtils.add(sum, tax.getTax()); // Taxes are already rounded...
            }
        } else {
            for (OrderLine line : order.getLines()) {
                sum =RoundUtils.add(sum, OrderLineHelper.getTax(line));
            }
        }
        return sum;
    }

    public static double getTotal(Order order) {
        return RoundUtils.add(getSubTotal(order) , getTax(order),order.getTotalExtendPrice());
    }

    public static double getTotalPaid(Order order) {
        double sum = 0.0;
        for (PaymentInfo p : order.getPayments()) {
            if (!"debtpaid".equals(p.getName())) {
                sum =RoundUtils.add(sum, p.getTotal());
            }
        }
        return sum;
    }
    
    public static double getTotalConsultValue(Order order){
    	double sum = 0.0;
    	for (OrderLine line : order.getLines()) {
            sum =RoundUtils.add(sum, OrderLineHelper.getConsultValue(line));
        }
        return sum;
    }

    public static IncludeTaxs getTaxLine(Order order,Tax tax) {

        for (IncludeTaxs taxline : order.getTaxes()) {
            if (tax.getId().equals(taxline.getTaxInfo().getId())) {
                return taxline;
            }
        }
        return new IncludeTaxs(tax);
    }

    public static String getTransactionID(Order order) {
        return (order.getPayments().size() > 0)
                ? (order.getPayments().get(order.getPayments().size() - 1)).getTransactionID()
                : StringUtils.getCardNumber(); //random transaction ID
    }

    public static  String getReturnMessage(Order order) {
        return ((order.getPayments().get(order.getPayments().size() - 1)) instanceof PaymentInfoMagcard)
                ? ((PaymentInfoMagcard) (order.getPayments().get(order.getPayments().size() - 1))).getReturnMessage()
                : LocalRes.getIntString("button.ok");
    }

    public static String printOrderName(Order order){
        String typeName="";
        if(Order.ORDERBEARING_REVERSE == order.orderBearing)
                typeName=order.defineType.getReverseName();
            else
                typeName=order.defineType.getName();
        String sHtml = "<tr><td width=\"30\">"+ "["+ order.m_iOrderId+"]" +"</td>" +
                "<td align=\"center\" width=\"100\">"+ typeName +"</td>" +
                "<td width=\"150\">"+ Formats.TIMESTAMP.formatValue(order.m_dDate) +"</td>" +
                "<td align=\"center\" width=\"100\">"+ printCustomer(order) +"</td>" +
                "<td align=\"center\" width=\"100\">"+ order.getLocationDesc() +"</td>" +
                "<td align=\"right\" width=\"100\">"+ Formats.CURRENCY.formatValue(order.totalPrice) +"</td>"+
                "<td width=\"100\">"+printUser(order)+"</td></tr>";
        return sHtml;
    }


     public static String printRefUser(Order order) {
        return order.reference_User == null ? "" : order.reference_User.getName();
    }


    public static String printCustomerAndAddr(Order order){
        return order.m_Customer == null ? "" : order.m_Customer.getName()+"-"+order.m_Customer.getAddress();
    }


    public static void writeExternal(Order o,ObjectOutput out) throws IOException {
        // esto es solo para serializar Orders que no estan en la bolsa de Orders pendientes
        out.writeObject(o.m_sId);
        out.writeInt(o.orderBearing);
        out.writeObject(o.m_iOrderId);
        out.writeObject(o.m_Customer);
        out.writeObject(o.m_dDate);
        out.writeObject(o.attributes);
        out.writeObject(o.m_aLines);
        out.writeDouble(o.m_dPriceRate);
        out.writeObject(o.attsetinstid);
        out.writeObject(o.defineType);
        out.writeObject(o.locationRef);
        out.writeObject(o.locationRef1);
        out.writeObject(o.memo);
        out.writeDouble(o.totalPrice);
        out.writeObject(o.refOrders);
        out.writeObject(o.reference_User);
        out.writeObject(o.states);
        out.writeObject(o.currentState);
        out.writeObject(o.m_User);
        out.writeObject(o.consultProductId);
        out.writeObject(o.consultProductAttsetinstid);
        out.writeObject(o.calcItems);
    }

    @SuppressWarnings("unchecked")
	public void readExternal(Order o,ObjectInput in) throws IOException, ClassNotFoundException {
        // esto es solo para serializar Orders que no estan en la bolsa de Orders pendientes
        o.m_sId = (String) in.readObject();
        o.orderBearing = in.readInt();
        o.m_iOrderId = (String) in.readObject();
        o.m_Customer = (BusinessPartner) in.readObject();
        o.m_dDate = (Date) in.readObject();
        o.attributes = (HashMap) in.readObject();
        o.m_aLines = (List<OrderLine>) in.readObject();
        o.m_dPriceRate=in.readDouble();
        o.attsetinstid=(String)in.readObject();
        o.defineType=(OrderType)in.readObject();

        o.locationRef=(String)in.readObject();
        o.locationRef1=(String)in.readObject();

        o.memo=(String)in.readObject();

        o.totalPrice=in.readDouble();
        o.refOrders=(ArrayList< com.openbravo.bean.erp.OrderRelation>)in.readObject();
        o.reference_User=(UserInfo)in.readObject();

        o.m_sActiveCash = null;

        o.payments = new ArrayList<PaymentInfo>();
        o.taxes = null;
        o.states=(List<OrderState>) in.readObject();
        o.currentState=(String) in.readObject();
        o.m_User = (UserInfo)in.readObject();
        o.consultProductId=(String) in.readObject();
        o.consultProductAttsetinstid=(String) in.readObject();
        o.calcItems=(List<com.openbravo.bean.erp.ordercalc.OrderCalcItem>)in.readObject();
    }
    
}
